package com.youngjun.common.oss.manager.impl;

import com.youngjun.common.exception.CommonExceptionType;
import com.youngjun.common.oss.expection.CommonException;
import com.youngjun.common.oss.manager.OssManager;
import io.minio.MinioClient;
import io.minio.errors.*;
import org.xmlpull.v1.XmlPullParserException;

import java.io.IOException;
import java.io.InputStream;
import java.security.InvalidKeyException;
import java.security.NoSuchAlgorithmException;
import java.util.Map;

/**
 * @author VirgoJun
 */
public class MinioOssManagerImpl implements OssManager {

    private String endpoint;
    private String accessKey;
    private String secretKey;

    public MinioOssManagerImpl(String endpoint, String accessKey, String secretKey) {
        this.endpoint = endpoint;
        this.accessKey = accessKey;
        this.secretKey = secretKey;
    }

    private MinioClient getMinioClient() throws InvalidPortException, InvalidEndpointException {
        return new MinioClient(endpoint, accessKey, secretKey);
    }

    @Override
    public void putObject(String bucketName, String objectName, String fileName, String contentType) {
        try {
            getMinioClient().putObject(bucketName, objectName, fileName, contentType);
        } catch (InvalidBucketNameException | NoSuchAlgorithmException | IOException | InvalidEndpointException | InsufficientDataException | NoResponseException | InvalidKeyException | InvalidArgumentException | InternalException | XmlPullParserException | InvalidPortException | ErrorResponseException e) {
            e.printStackTrace();
            throw new CommonException(CommonExceptionType.OSS_INSERT_FAILED);
        }
    }

    @Override
    public void putObject(String bucketName, String objectName, String fileName) {
        this.putObject(bucketName, objectName, fileName, null);
    }

    @Override
    public void putObject(String bucketName, String objectName, InputStream stream, long size, String contentType) {
        try {
            getMinioClient().putObject(bucketName, objectName, stream, size, contentType);
        } catch (InvalidBucketNameException | NoSuchAlgorithmException | IOException | InvalidEndpointException | InsufficientDataException | NoResponseException | InvalidKeyException | InvalidArgumentException | InternalException | XmlPullParserException | InvalidPortException | ErrorResponseException e) {
            e.printStackTrace();
            throw new CommonException(CommonExceptionType.OSS_INSERT_FAILED);
        }
    }

    @Override
    public void putObject(String bucketName, String objectName, InputStream stream, long size, Map<String, String> headerMap) {
        try {
            getMinioClient().putObject(bucketName, objectName, stream, size, headerMap);
        } catch (InvalidBucketNameException | NoSuchAlgorithmException | IOException | InvalidEndpointException | InsufficientDataException | NoResponseException | InvalidKeyException | InvalidArgumentException | InternalException | XmlPullParserException | InvalidPortException | ErrorResponseException e) {
            e.printStackTrace();
            throw new CommonException(CommonExceptionType.OSS_INSERT_FAILED);
        }
    }

    @Override
    public void putObject(String bucketName, String objectName, InputStream stream, String contentType) {
        try {
            getMinioClient().putObject(bucketName, objectName, stream, contentType);
        } catch (InvalidBucketNameException | NoSuchAlgorithmException | IOException | InvalidEndpointException | InsufficientDataException | NoResponseException | InvalidKeyException | InvalidArgumentException | InternalException | XmlPullParserException | InvalidPortException | ErrorResponseException e) {
            e.printStackTrace();
            throw new CommonException(CommonExceptionType.OSS_INSERT_FAILED);
        }
    }

    @Override
    public String getObjectUrl(String bucketName, String objectName) {
        try {
            return getMinioClient().getObjectUrl(bucketName, objectName);
        } catch (InvalidBucketNameException | NoSuchAlgorithmException | IOException | InvalidEndpointException | InsufficientDataException | NoResponseException | InvalidKeyException | InternalException | XmlPullParserException | InvalidPortException | ErrorResponseException e) {
            e.printStackTrace();
            throw new CommonException(CommonExceptionType.OSS_GET_FAILED);
        }
    }

    @Override
    public InputStream getObject(String bucketName, String objectName) {
        try {
            return getMinioClient().getObject(bucketName, objectName);
        } catch (InvalidBucketNameException | NoSuchAlgorithmException | IOException | InvalidEndpointException | InsufficientDataException | NoResponseException | InvalidKeyException | InvalidArgumentException | InternalException | XmlPullParserException | InvalidPortException | ErrorResponseException e) {
            e.printStackTrace();
            throw new CommonException(CommonExceptionType.OSS_GET_FAILED);
        }
    }

    @Override
    public InputStream getObject(String bucketName, String objectName, long offset) {
        try {
            return getMinioClient().getObject(bucketName, objectName, offset);
        } catch (InvalidBucketNameException | NoSuchAlgorithmException | IOException | InvalidEndpointException | InsufficientDataException | NoResponseException | InvalidKeyException | InvalidArgumentException | InternalException | XmlPullParserException | InvalidPortException | ErrorResponseException e) {
            e.printStackTrace();
            throw new CommonException(CommonExceptionType.OSS_GET_FAILED);
        }
    }

    @Override
    public InputStream getObject(String bucketName, String objectName, long offset, Long length) {
        try {
            return getMinioClient().getObject(bucketName, objectName, offset, length);
        } catch (InvalidBucketNameException | NoSuchAlgorithmException | IOException | InvalidEndpointException | InsufficientDataException | NoResponseException | InvalidKeyException | InvalidArgumentException | InternalException | XmlPullParserException | InvalidPortException | ErrorResponseException e) {
            e.printStackTrace();
            throw new CommonException(CommonExceptionType.OSS_GET_FAILED);
        }
    }

    @Override
    public void getObject(String bucketName, String objectName, String fileName) {
        try {
            getMinioClient().getObject(bucketName, objectName, fileName);
        } catch (InvalidBucketNameException | NoSuchAlgorithmException | IOException | InvalidEndpointException | InsufficientDataException | NoResponseException | InvalidKeyException | InvalidArgumentException | InternalException | XmlPullParserException | InvalidPortException | ErrorResponseException e) {
            e.printStackTrace();
            throw new CommonException(CommonExceptionType.OSS_GET_FAILED);
        }
    }

    @Override
    public void removeObject(String bucketName, String objectName) {
        try {
            getMinioClient().removeObject(bucketName, objectName);
        } catch (InvalidBucketNameException | NoSuchAlgorithmException | IOException | InsufficientDataException | InvalidKeyException | NoResponseException | XmlPullParserException | InternalException | ErrorResponseException | InvalidPortException | InvalidArgumentException | InvalidEndpointException e) {
            e.printStackTrace();
            throw new CommonException(CommonExceptionType.OSS_REMOVE_FAILED);

        }
    }

    @Override
    public void removeObject(String bucketName, Iterable<String> objectNames) {
        try {
            getMinioClient().removeObject(bucketName, objectNames);
        } catch (InvalidPortException | InvalidEndpointException e) {
            e.printStackTrace();
            throw new CommonException(CommonExceptionType.OSS_REMOVE_FAILED);
        }
    }
}
